package com.jellyfishumbrella;

import java.awt.AlphaComposite;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Polygon;
import java.awt.RenderingHints;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.awt.event.MouseWheelEvent;
import java.awt.event.MouseWheelListener;
import java.awt.geom.Rectangle2D;
import java.awt.image.BufferedImage;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.PriorityQueue;
import java.util.Random;

import javax.swing.JTextField;

import be.humphreys.simplevoronoi.Cell;
import be.humphreys.simplevoronoi.GraphEdge;
import be.humphreys.simplevoronoi.LandscapeSite;
import be.humphreys.simplevoronoi.Voronoi;
import be.humphreys.simplevoronoi.VoronoiOutput;

import com.jellyfishumbrella.noise.Noise;

public class LandscapeBufferedImage extends BufferedImage {
	private static final double		TOO_CLOSE		= 20 * GameLogic.SCALING;
	private static final int		WIDTH			= (int) Math.floor(600 * GameLogic.SCALING);
	private static final int		HEIGHT			= (int) Math.floor(600 * GameLogic.SCALING);
	Graphics2D						g2;
	public HashMap<String, String>	debugData		= new HashMap<String, String>();
	public LandscapeData			data			= null;

	public boolean					drawCorners		= false;
	public boolean					drawSites		= false;
	public boolean					drawCoastEdges	= true;
	public boolean					fillCells		= true;
	public boolean					outlineCells	= false;
	public boolean					drawRivers		= true;

	public LandscapeBufferedImage(int width, int height, int imageType) {
		super(width, height, imageType);

		g2 = (Graphics2D) this.createGraphics();

		RenderingHints rh = new RenderingHints(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);

		rh.put(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);

		g2.setRenderingHints(rh);

	}
/*
	public void doDraw() {
		System.out.println("drawing");

		BasicStroke thin = new BasicStroke(0.5f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_ROUND, 10.0f, null, 0.0f);
		g2.setStroke(thin);
		if (data != null) {
			HashMap<Site, Cell> cells = data.rawOutput.toCells();

			synchronized (data.rawOutput) {

				for (Map.Entry<Site, Cell> entry : cells.entrySet()) {
					LandscapeSite currSite = (LandscapeSite) entry.getKey();
					Cell currCell = (Cell) entry.getValue();

					for (int i = 0; i < currCell.edges.size(); i++) {
						GraphEdge currEdge = currCell.edges.get(i);

						if (fillCells) {
							fillCells(currCell, currSite, currEdge);
						}
						if (outlineCells) {
							outlineCells(currEdge);
						}
						if (drawCoastEdges) {
							drawCoastEdges(currEdge);
						}
					}
					if (drawSites) {
						drawSites(currSite);
					}
					if (drawCorners) {
						drawCorners();
					}
				}
			}
		}
	}
*/
	public void fillCells(Cell currCell, LandscapeSite currSite, GraphEdge currEdge) {
		Polygon p = new Polygon();
		p.addPoint((int) Math.round(currSite.x / GameLogic.SCALING), (int) Math.round(currSite.y / GameLogic.SCALING));
		p.addPoint((int) Math.round(currEdge.corner1.x / GameLogic.SCALING), (int) Math.round(currEdge.corner1.y / GameLogic.SCALING));
		p.addPoint((int) Math.round(currEdge.corner2.x / GameLogic.SCALING), (int) Math.round(currEdge.corner2.y / GameLogic.SCALING));

		float r, g, b;
		if (currCell.isWater()) {
			//r = (float) Math.min(1.0, (currSite.alt / data.maxAlt));
			//g = (float) Math.min(1.0, (currSite.alt / data.maxAlt));
			b = 1.0f;
			if (currSite.isOcean) {
				b /= 1.5f;
			} else {
			}
		} else {
			//r = (float) Math.min(1.0, (currSite.alt / data.maxAlt));
			//g = (float) Math.min(1.0, (currSite.alt / data.maxAlt));
			//b = (float) Math.min(1.0, (currSite.alt / data.maxAlt));
		}
		//g2.setColor(new Color(r, g, b));
		g2.fillPolygon(p);
	}

	public void outlineCells(GraphEdge currEdge) {
		g2.setColor(Color.LIGHT_GRAY);
		g2.drawLine((int) Math.round(currEdge.corner1.x / GameLogic.SCALING), (int) Math.round(currEdge.corner1.y / GameLogic.SCALING), (int) Math.round(currEdge.corner2.x / GameLogic.SCALING),
				(int) Math.round(currEdge.corner2.y / GameLogic.SCALING));
	}

	public void drawCoastEdges(GraphEdge currEdge) {
		if (currEdge.corner1.isCoast && currEdge.corner2.isCoast) {
			g2.setColor(new Color(.75f, .75f, 0.25f));
			g2.setStroke(new BasicStroke(2, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND));
			g2.drawLine((int) Math.round(currEdge.corner1.x / GameLogic.SCALING), (int) Math.round(currEdge.corner1.y / GameLogic.SCALING), (int) Math.round(currEdge.corner2.x / GameLogic.SCALING),
					(int) Math.round(currEdge.corner2.y / GameLogic.SCALING));
		} else {
			if (currEdge.corner1.weight > 0 && currEdge.corner2.weight > 0) {
				float lineWidth = 2;
				g2.setColor(new Color(0.1f, 0.3f, 1.0f));
				g2.setStroke(new BasicStroke(lineWidth, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND));
				g2.drawLine((int) Math.round(currEdge.corner1.x / GameLogic.SCALING), (int) Math.round(currEdge.corner1.y / GameLogic.SCALING), (int) Math.round(currEdge.corner2.x / GameLogic.SCALING),
						(int) Math.round(currEdge.corner2.y / GameLogic.SCALING));
			}
		}
	}

	public void drawSites(LandscapeSite currSite) {
		g2.setColor(Color.DARK_GRAY);
		g2.fillOval((int) Math.round(currSite.x / GameLogic.SCALING) - 2, (int) Math.round(currSite.y / GameLogic.SCALING) - 2, 4, 4);
	}
/*
	public void drawCorners() {
		int radius = 1;
		for (int i = 0; i < data.drawCorners.size(); i++) {
			g2.drawOval((int) Math.round(data.drawCorners.get(i).x / GameLogic.SCALING) - radius / 2, (int) Math.round(data.drawCorners.get(i).y / GameLogic.SCALING) - radius / 2, radius, radius);
		}
	}
	*/
}
